#!/usr/bin/env python

# copyright 2010 Studio Cypher, LLC
# developer: Will Emigh
# projects@studiocypher.com

# Custom modules
from authentication import user_required
from authentication import get_account_from_user
from models import Account
from models import TradeRecord
from models import Colony
from models import ColonyShip
from models import RecyclingShip
from models import FreighterShip
from models import UnitType
from models import Log

# Built-in or Google modules
import cgi
import os
#import imghdr
from google.appengine.ext.webapp import template
from google.appengine.api import images
from google.appengine.ext import webapp
from google.appengine.ext.webapp.util import run_wsgi_app
from google.appengine.api import users
from google.appengine.ext import db
  

class CreateOffer(webapp.RequestHandler):
    def get(self):
        user = users.get_current_user()
        ownerAccount = get_account_from_user(user)
        
        accountKey = self.request.get("recip_key")
        recipAccount = Account.get(db.Key(accountKey))
            
        if recipAccount:        

            template_values = {
            'ownerAccount': ownerAccount,
            'recipAccount': recipAccount,
            }

            path = os.path.join(os.path.dirname(__file__), 'trade.html')
            self.response.out.write(template.render(path, template_values))
        

class AcceptOffer(webapp.RequestHandler):
    def get(self):
        offerKey = self.request.get("offer_key")
        thisOffer = TradeRecord.get(db.Key(offerKey))
        if (thisOffer):
            takeAccount = Account.get(db.Key(thisOffer.to))
            allColonies = Colony.all()
            allColonies = allColonies.filter('owner =', takeAccount).filter('location =', thisOffer.location)
            takeColony = allColonies[0]
            resPkg = takeColony.resourceStorage

        # get goods from offer for recipient
            resPkg.resourceOne += thisOffer.give_resOne
            resPkg.resourceTwo += thisOffer.give_resTwo
            resPkg.resourceThree += thisOffer.give_resThree
            resPkg.resourceFour += thisOffer.give_resFour
            resPkg.put()
            
            for i in range(thisOffer.give_colonyShips):
                #create a new ship 
                types = UnitType.all()
                shipstype = types.filter('type =','ColonyS')
                shipstype = shipstype[0]
                cs = ColonyShip(owner = takeAccount, planet = thisOffer.location, type = shipstype)
                cs.put()
                cs.name = "ColonyShip #"+str(cs.key().id())
                cs.put()
            
            for i in range(thisOffer.give_recyclerShips):
                #create a new ship 
                types = UnitType.all()
                shipstype = types.filter('type =','RecyclingS')
                shipstype = shipstype[0]
                cs = RecyclingShip(owner = takeAccount, planet = thisOffer.location, type = shipstype)
                cs.put()
                cs.name = "RecyclingShip #"+str(cs.key().id())
                cs.put()
            
            for i in range(thisOffer.give_freighterShips):
                #create a new ship 
                types = UnitType.all()
                shipstype = types.filter('type =','FreighterS')
                shipstype = shipstype[0]
                cs = FreighterShip(owner = takeAccount, planet = thisOffer.location, type = shipstype)
                cs.put()
                cs.name = "FreighterShip #"+str(cs.key().id())
                cs.put()
        
        
        # put goods to offer owner
            ownerColony = Colony.get_colony(thisOffer.owner, thisOffer.location)
            resPkg = ownerColony.resourceStorage
            
            resPkg.resourceOne += thisOffer.take_resOne
            resPkg.resourceTwo += thisOffer.take_resTwo
            resPkg.resourceThree += thisOffer.take_resThree
            resPkg.resourceFour += thisOffer.take_resFour
            resPkg.put()
            #log action
            new_log = Log.log(thisOffer.owner.email, "uploaded resources", thisOffer.location.name, 
                              "Resources after accepting the trade Minerals: " + str(resPkg.resourceOne) + 
                              " Water: " + str(resPkg.resourceTwo) +
                              " Fuels: " + str(resPkg.resourceThree) +
                              " Organic: " + str(resPkg.resourceFour))
            #end of log action
            
            for i in range(thisOffer.take_colonyShips):
                #create a new ship 
                types = UnitType.all()
                shipstype = types.filter('type =','ColonyS')
                shipstype = shipstype[0]
                cs = ColonyShip(owner = takeAccount, planet = thisOffer.location, type = shipstype)
                cs.put()
                cs.name = "ColonyShip #"+str(cs.key().id())
                cs.put()
            
            for i in range(thisOffer.take_recyclerShips):
                #create a new ship 
                types = UnitType.all()
                shipstype = types.filter('type =','RecyclingS')
                shipstype = shipstype[0]
                cs = RecyclingShip(owner = takeAccount, planet = thisOffer.location, type = shipstype)
                cs.put()
                cs.name = "RecyclingShip #"+str(cs.key().id())
                cs.put()
            
            for i in range(thisOffer.take_freighterShips):
                #create a new ship 
                types = UnitType.all()
                shipstype = types.filter('type =','FreighterS')
                shipstype = shipstype[0]
                cs = FreighterShip(owner = takeAccount, planet = thisOffer.location, type = shipstype)
                cs.put()
                cs.name = "FreighterShip #"+str(cs.key().id())
                cs.put()

            # remove goods from taker

            recipColony = Colony.get_colony(takeAccount, thisOffer.location)
            
            recipColony.resourceStorage.resourceOne -= thisOffer.take_resOne
            recipColony.resourceStorage.resourceTwo -= thisOffer.take_resTwo
            recipColony.resourceStorage.resourceThree -= thisOffer.take_resThree
            recipColony.resourceStorage.resourceFour -= thisOffer.take_resFour
            recipColony.resourceStorage.put()
            #log action
            new_log = Log.log(thisOffer.owner.email, "uploaded resources", thisOffer.location.name, 
                              "Resources after the trade is accepted by other player the trade Minerals: " + str(recipColony.resourceStorage.resourceOne) + 
                              " Water: " + str(recipColony.resourceStorage.resourceTwo) +
                              " Fuels: " + str(recipColony.resourceStorage.resourceThree) +
                              " Organic: " + str(recipColony.resourceStorage.resourceFour))
            #end of log action
            
            cs = ColonyShip.all()
            cs = cs.filter('owner =', takeAccount).filter('planet =', thisOffer.location)
            for i in range(thisOffer.give_colonyShips):
            # delete all ships
                thisShip = cs.fetch(1)
                thisShip.delete()
            
            rs = RecyclingShip.all()
            rs = rs.filter('owner =', takeAccount).filter('planet =', thisOffer.location)
            for i in range(thisOffer.give_recyclerShips):
                # delete all ships
                thisShip = rs.fetch(1)
                thisShip.delete()
            
            fs = FreighterShip.all()
            fs = fs.filter('owner =', takeAccount).filter('planet =', thisOffer.location)
            for i in range(thisOffer.give_freighterShips):
                # delete all ships
                thisShip = fs.fetch(1)
                thisShip.delete()
       
            thisOffer.delete()
        
        self.redirect("/profiler/private?res_type=5");
        
        
        
        
        
        
        
class RejectOffer(webapp.RequestHandler):
    def get(self):
        offerKey = self.request.get("offer_key")
        thisOffer = TradeRecord.get(db.Key(offerKey))
        if (thisOffer):
            ownerColony = Colony.get_colony(thisOffer.owner, thisOffer.location)
            resPkg = ownerColony.resourceStorage
            
            resPkg.resourceOne += thisOffer.give_resOne
            resPkg.resourceTwo += thisOffer.give_resTwo
            resPkg.resourceThree += thisOffer.give_resThree
            resPkg.resourceFour += thisOffer.give_resFour
            resPkg.put()
            
            for i in range(thisOffer.give_colonyShips):
                #create a new ship 
                types = UnitType.all()
                shipstype = types.filter('type =','ColonyS')
                shipstype = shipstype[0]
                cs = ColonyShip(owner = account, planet = thisOffer.location, type = shipstype)
                cs.put()
                cs.name = "ColonyShip #"+str(cs.key().id())
                cs.put()
            
            for i in range(thisOffer.give_recyclerShips):
                #create a new ship 
                types = UnitType.all()
                shipstype = types.filter('type =','RecyclingS')
                shipstype = shipstype[0]
                cs = RecyclingShip(owner = account, planet = thisOffer.location, type = shipstype)
                cs.put()
                cs.name = "RecyclingShip #"+str(cs.key().id())
                cs.put()
            
            for i in range(thisOffer.give_freighterShips):
                #create a new ship 
                types = UnitType.all()
                shipstype = types.filter('type =','FreighterS')
                shipstype = shipstype[0]
                cs = FreighterShip(owner = account, planet = thisOffer.location, type = shipstype)
                cs.put()
                cs.name = "FreighterShip #"+str(cs.key().id())
                cs.put()

        
            thisOffer.delete()
        
        self.redirect("/profiler/private?res_type=5");
        
        
        
class ViewOffer(webapp.RequestHandler):
    def get(self):
        offerKey = self.request.get("offer_key")
        thisOffer = TradeRecord.get(db.Key(offerKey))
        
        if thisOffer:
            # validate offer for taker
            valid_offer = True
            good_offer = False
            
            takeAccount = Account.get(db.Key(thisOffer.to))
            allColonies = Colony.all()
            allColonies = allColonies.filter('owner =', takeAccount).filter('location =', thisOffer.location)
            takeColony = allColonies[0]
            resPkg = takeColony.resourceStorage
            
            # does the recipient have enough goods for a trade?
            if( thisOffer.take_resOne > 0 ):
                if( resPkg.resourceOne < thisOffer.take_resOne ):
                    valid_offer = False
                    
            if( thisOffer.take_resTwo > 0 ):
                if( resPkg.resourceTwo < thisOffer.take_resTwo ):
                    valid_offer = False
                    
            if( thisOffer.take_resThree > 0 ):
                if( resPkg.resourceThree < thisOffer.take_resThree ):
                    valid_offer = False
                    
            if( thisOffer.take_resFour > 0 ):
                if( resPkg.resourceFour < thisOffer.take_resFour ):
                    valid_offer = False
                    
            if( thisOffer.take_colonyShips > 0 ):
                # get count of colony ships on this planet
                allColonyShips = ColonyShip.all()
                myColonyShips = allColonyShips.filter('planet =', thisOffer.location).filter('owner =', takeAccount.key())
                if( thisOffer.take_colonyShips > myColonyShips.count() ):
                    valid_offer = False
                    
            if( thisOffer.take_recyclerShips > 0 ):
                # get count of colony ships on this planet
                allRecyclingShips = RecyclingShip.all()
                myRecyclingShips = allRecyclingShips.filter('planet =', thisOffer.location).filter('owner =', takeAccount.key())
                if( thisOffer.take_recyclerShips > myRecyclingShips.count() ):
                    valid_offer = False
                    
            if( thisOffer.take_freighterShips > 0 ):
                # get count of colony ships on this planet
                allFreighterShips = FreighterShip.all()
                myFrieghterShips = allFreighterShips.filter('planet =', thisOffer.location).filter('owner =', takeAccount.key())
                if( thisOffer.take_freighterShips > myFrieghterShips.count() ):
                    valid_offer = False

            status_msg = ""
            if ( not valid_offer ):
                status_msg = "You do not have enough goods for this trade!"
            recipAccount = Account.get(db.Key(thisOffer.to))  
				
            template_values = {
                'offer': thisOffer,
                'offer_acceptable': valid_offer,
                'recipAccount': recipAccount,
                'status_message': status_msg,
                }

            path = os.path.join(os.path.dirname(__file__), 'trade_receive.html')
            self.response.out.write(template.render(path, template_values))
        
        else:
            self.redirect("/admin/login")
            

class ProcessOffer(webapp.RequestHandler):
    def post(self):
        user = users.get_current_user()
        ownerAccount = get_account_from_user(user)
        accountKey = self.request.get("account_key")
        recipAccount = Account.get(db.Key(accountKey))
            
        if recipAccount: 
            # create new TradeRecord
            myTradeRecord = TradeRecord()
            myTradeRecord.owner = ownerAccount           
            myTradeRecord.location = ownerAccount.current_planet          
            myTradeRecord.to = str(recipAccount.key())
            myTradeRecord.message = self.request.get("message")
            
            
            # get data from form CGI
            # GIVE
            myTradeRecord.give_resOne = int(self.request.get("give_resOne") )           
            myTradeRecord.give_resTwo = int(self.request.get("give_resTwo"))            
            myTradeRecord.give_resThree = int(self.request.get("give_resThree"))            
            myTradeRecord.give_resFour = int(self.request.get("give_resFour"))            
            myTradeRecord.give_colonyShips = int(self.request.get("give_colonyShips"))            
            myTradeRecord.give_recyclerShips = int(self.request.get("give_recyclerShips"))            
            myTradeRecord.give_freighterShips = int(self.request.get("give_freighterShips")) 
            
            # validate input
            valid_offer = True
            good_offer = False
            ownerColony = Colony.get_colony(ownerAccount, myTradeRecord.location)
            
            if( myTradeRecord.give_resOne > 0 ):
                good_offer = True
                if( ownerColony.resourceStorage.resourceOne < myTradeRecord.give_resOne ):
                    valid_offer = False
                    
            if( myTradeRecord.give_resTwo > 0 ):
                good_offer = True
                if( ownerColony.resourceStorage.resourceTwo < myTradeRecord.give_resTwo ):
                    valid_offer = False
                    
            if( myTradeRecord.give_resThree > 0 ):
                good_offer = True
                if( ownerColony.resourceStorage.resourceThree < myTradeRecord.give_resThree ):
                    valid_offer = False
                    
            if( myTradeRecord.give_resFour > 0 ):
                good_offer = True
                if( ownerColony.resourceStorage.resourceFour < myTradeRecord.give_resFour ):
                    valid_offer = False
                                        
            if( myTradeRecord.give_colonyShips > 0 ):
                good_offer = True
                # get count of colony ships on this planet
                allColonyShips = ColonyShip.all()
                myColonyShips = allColonyShips.filter('planet =', myTradeRecord.location).filter('owner =', ownerAccount.key())
                if( myTradeRecord.give_colonyShips > myColonyShips.count() ):
                    valid_offer = False
                    
            if( myTradeRecord.give_recyclerShips > 0 ):
                good_offer = True
                # get count of colony ships on this planet
                allRecyclingShips = RecyclingShip.all()
                myRecyclingShips = allRecyclingShips.filter('planet =', myTradeRecord.location).filter('owner =', ownerAccount.key())
                if( myTradeRecord.give_recyclerShips > myRecyclingShips.count() ):
                    valid_offer = False
                    
            if( myTradeRecord.give_freighterShips > 0 ):
                good_offer = True
                # get count of colony ships on this planet
                allFreighterShips = FreighterShip.all()
                myFrieghterShips = allFreighterShips.filter('planet =', myTradeRecord.location).filter('owner =', ownerAccount.key())
                if( myTradeRecord.take_freighterShips >= myFrieghterShips.count() ):
                    valid_offer = False            
            
            if( good_offer ):
                if( valid_offer ):
            # remove goods from owner colony
                    ownerColony = Colony.get_colony(myTradeRecord.owner, myTradeRecord.location)
            
                    ownerColony.resourceStorage.resourceOne -= myTradeRecord.give_resOne
                    ownerColony.resourceStorage.resourceTwo -= myTradeRecord.give_resTwo
                    ownerColony.resourceStorage.resourceThree -= myTradeRecord.give_resThree
                    ownerColony.resourceStorage.resourceFour -= myTradeRecord.give_resFour
                    ownerColony.resourceStorage.put()
            
                    cs = ColonyShip.all()
                    cs = cs.filter('owner =', ownerAccount).filter('planet =', myTradeRecord.location)
                    for i in range(myTradeRecord.give_colonyShips):
                # delete all ships
                        thisShip = cs.fetch(1)
                        thisShip.delete()
            
                    rs = RecyclingShip.all()
                    rs = rs.filter('owner =', ownerAccount).filter('planet =', myTradeRecord.location)
                    for i in range(myTradeRecord.give_recyclerShips):
                # delete all ships
                        thisShip = rs.fetch(1)
                        thisShip.delete()
            
                    fs = FreighterShip.all()
                    fs = fs.filter('owner =', ownerAccount).filter('planet =', myTradeRecord.location)
                    for i in range(myTradeRecord.give_freighterShips):
                # delete all ships
                        thisShip = fs.fetch(1)
                        thisShip.delete()
            

            # TAKE
            myTradeRecord.take_resOne = int(self.request.get("take_resOne") )           
            myTradeRecord.take_resTwo = int(self.request.get("take_resTwo"))            
            myTradeRecord.take_resThree = int(self.request.get("take_resThree"))            
            myTradeRecord.take_resFour = int(self.request.get("take_resFour"))            
            myTradeRecord.take_colonyShips = int(self.request.get("take_colonyShips"))            
            myTradeRecord.take_recyclerShips = int(self.request.get("take_recyclerShips"))            
            myTradeRecord.take_freighterShips = int(self.request.get("take_freighterShips")) 
            
            if( valid_offer and good_offer):
                myTradeRecord.put()

            template_values = {
            'recipAccount': recipAccount,
            }
            url = "/profiler/public?account_key="+str(recipAccount.key())
            self.redirect(url)
        else:
            self.redirect("/")
  
  

application = webapp.WSGIApplication(
                                     [('/trade/create_offer', CreateOffer),
                                     ('/trade/view_offer', ViewOffer),
                                     ('/trade/accept_offer', AcceptOffer),
                                     ('/trade/reject_offer', RejectOffer),
                                     ('/trade/process_offer', ProcessOffer),],
                                     debug=True)									 
def main():
    run_wsgi_app(application)

if __name__ == "__main__":
    main()
